from django.template import RequestContext
from django.http import HttpResponse, HttpResponseRedirect, HttpResponseBadRequest, HttpResponseForbidden
from django.core.urlresolvers import reverse
from django.shortcuts import render_to_response,redirect,render, get_object_or_404
from django.views.decorators.csrf import csrf_exempt
from django.utils.encoding import smart_str
from django.contrib import auth, messages
from django.contrib.auth.models import User, Group
from django.contrib.auth.decorators import login_required
from account.models import *
from disn.utilities import *
from decimal import Decimal, getcontext
from django.contrib import auth, messages
from django.contrib.auth.decorators import login_required
from disn.settings import BASE_DIR, DEBUG, redis_instance
from disn.settings import get_book_subscription_wechat_client, get_book_service_wechat_client
from disn.settings import BOOK_SUBSCRIPTION_APPID, BOOK_SUBSCRIPTION_TOKEN, BOOK_SUBSCRIPTION_APPSECRET, BOOK_SUBSCRIPTION_ENCODING_AES_KEY
from disn.settings import BOOK_SERVICE_APPID, BOOK_SERVICE_TOKEN, BOOK_SERVICE_APPSECRET, BOOK_SERVICE_ENCODING_AES_KEY
from urllib.parse import unquote, quote
from wechatpy import parse_message
from wechatpy.utils import check_signature, ObjectDict
from wechatpy.exceptions import InvalidSignatureException
from wechatpy.crypto import WeChatCrypto
from wechatpy.exceptions import InvalidSignatureException, InvalidAppIdException, WeChatClientException
from wechatpy.replies import TextReply, ImageReply, VoiceReply, ArticlesReply
from wechatpy.messages import *
from wechatpy.events   import *
import sys,hashlib,logging,uuid,json,os,traceback,time, random, string, requests
from io import BytesIO

log = logging.getLogger(__name__)
log.setLevel(logging.INFO)


@csrf_exempt
def service(request):
    log.info('function service reload')
    wechat = get_book_service_wechat_client()
    echostr = request.GET.get('echostr', None)
    signature = request.GET.get('signature')
    msg_signature = request.GET.get('msg_signature')
    timestamp = request.GET.get('timestamp')
    nonce = request.GET.get('nonce')
    if request.method == 'GET' and echostr is not None and echostr != '':
        log.info('Starting check_signature ...')
        try:
            check_signature(BOOK_SERVICE_TOKEN, signature, timestamp, nonce)
            return HttpResponse(echostr, content_type="text/plain")
        except InvalidSignatureException:
            return HttpResponseForbidden()
    xml = request.body
    # log.info('xml=%s' %xml)
    crypto = WeChatCrypto(BOOK_SERVICE_TOKEN, BOOK_SERVICE_ENCODING_AES_KEY, BOOK_SERVICE_APPID)
    try:
        decrypted_xml = crypto.decrypt_message(xml, msg_signature, timestamp, nonce)
    except (InvalidAppIdException, InvalidSignatureException):
        return HttpResponseForbidden()
    msg = parse_message(decrypted_xml)
    source = msg.source
    log.info('*' * 8 + 'book service user [%s], msg.type:%s' %(source, msg.type) + '*' * 8)
    if isinstance(msg, TextMessage):
        log.info('Received type(%s) msg: %s' %(msg.type, msg.content))
    if isinstance(msg, BaseEvent):
        log.info('Received type(%s) msg: %s' %(msg.type, msg.event))
    log.info('*' * 80)
    if isinstance(msg, UnsubscribeEvent):
        redis_instance.delete(source)
        # notify admin
        return HttpResponse('unsubscribe')
    elif isinstance(msg, SubscribeEvent):
        redis_instance.set(source, sid())
    response = None
    reply_msg = receive_msg = ''

    save_path = './media/book/service/attachments/%s/' % source
    link_path = None
    file_name = sid()
    if not os.path.exists(save_path):
        os.makedirs(save_path)
    book_service_admin, book_service_admin_created = WxConfig.objects.get_or_create(key='book_service_admin',status='1',category='3')
    if isinstance(msg, TextMessage):
        receive_text = msg.content.strip()
        if book_service_admin is not None and source == book_service_admin.value:
            if receive_text == 'update_menu':
                menu_config, menu_config_created = WxConfig.objects.get_or_create(key='book_menu', status='1', category='4')
                if menu_config_created:
                    response = TextReply(content='新建菜单变量[book_menu],请设置value', message=msg)
                else:
                    wechat.menu.create(eval(menu_config.value))
                    response = TextReply(content='微信菜单更新成功！', message=msg)
            else:
                try:
                    config = WxConfig.objects.get(key='book_%s' %receive_text,status='1',category='3')
                    if config.reply_type == 'text':
                        reply_msg = config.value
                        response = TextReply(content=reply_msg, message=msg)
                    elif config.reply_type == 'news':
                        response = ArticlesReply(articles=eval(config.value), message=msg)
                    elif config.reply_type == 'voice':
                        pass
                    elif config.reply_type == 'image':
                        pass
                    elif config.reply_type == 'video':
                        pass
                except WxConfig.DoesNotExist:
                    config = WxConfig()
                    config.key = 'book_%s' %receive_text
                    config.value = 'book_%s' %receive_text
                    config.status = '1'
                    config.category = '3'
                    config.save()
                    response = TextReply(content='新建微信自定义字符串[%s]' %config.key, message=msg)
        else:
            try:
                config = WxConfig.objects.get(key='book_%s' %receive_text,status='1',category='3')
            except WxConfig.DoesNotExist:
                try:
                    config = WxConfig.objects.get(key='book_auto_reply_text',status='1',category='3')
                except WxConfig.DoesNotExist:
                    config = WxConfig()
                    config.key = 'book_auto_reply_text'
                    config.value = '我们已经收到您的留言。谢谢！'
                    config.status = '1'
                    config.category = '3'
                    config.save()
            receive_msg = '%s(%s)' %(receive_text, msg.type)
            if config.reply_type == 'text':
                response = TextReply(content=config.value, message=msg)
            elif config.reply_type == 'news':
                response = ArticlesReply(articles=eval(config.value), message=msg)
            elif config.reply_type == 'voice':
                pass
            elif config.reply_type == 'image':
                pass
            elif config.reply_type == 'video':
                pass
    elif isinstance(msg, VoiceMessage):
        receive_text = msg.recognition
        try:
            config = WxConfig.objects.get(key='book_%s' %receive_text, status='1', category='3')
        except WxConfig.DoesNotExist:
            try:
                config = WxConfig.objects.get(key='book_auto_reply_voice',status='1',category='3')
            except WxConfig.DoesNotExist:
                config = WxConfig()
                config.key = 'book_auto_reply_voice'
                config.value = '我们已经收到您的语音留言。'
                config.status = '1'
                config.category = '3'
                config.save()
        receive_msg = '%s(%s)' %(receive_text, msg.type)
        reply_msg = config.value
        response = TextReply(content=reply_msg, message=msg)
        resp = wechat.media.download(msg.media_id)
        save_path = '%s%s.%s' %(save_path, file_name, msg.format)
        link_path = './book/service/attachments/%s/' % source
        link_path = '%s%s.amr' %(link_path,file_name)
        log.info('save_path=%s' %save_path) # file_path=./book/service/attachments/jezhang/150611114353137791.jpg
        with open(save_path, 'wb') as fd:
            for chunk in resp.iter_content(1024):
                fd.write(chunk)
    elif isinstance(msg, ImageMessage):
        try:
            config = WxConfig.objects.get(key='book_auto_reply_image',status='1',category='3')
        except WxConfig.DoesNotExist:
            config = WxConfig()
            config.key = 'book_auto_reply_image'
            config.value = '我们已经收到您的图片。'
            config.status = '1'
            config.category = '3'
            config.save()
        reply_msg = config.value
        response = TextReply(content=reply_msg, message=msg)
        receive_msg = '收到图片(%s)' %msg.type
        resp = wechat.media.download(msg.media_id)
        save_path = '%s%s.jpg' %(save_path,file_name)
        link_path = './book/service/attachments/%s/' % source
        link_path = '%s%s.jpg' %(link_path,file_name)
        log.info('save_path=%s' %save_path)
        with open(save_path, 'wb') as fd:
            for chunk in resp.iter_content(1024):
                fd.write(chunk)
    elif isinstance(msg, VideoMessage):
        try:
            config = WxConfig.objects.get(key='book_auto_reply_video',status='1',category='3')
        except WxConfig.DoesNotExist:
            config = WxConfig()
            config.key = 'book_auto_reply_video'
            config.value = '我们已经收到您的视频。'
            config.status = '1'
            config.category = '3'
            config.save()
        reply_msg = config.value
        response = TextReply(content=reply_msg, message=msg)
        receive_msg = '收到视频(%s)' %msg.type
        resp = wechat.media.download(msg.media_id)
        save_path = '%s%s.mp4' %(save_path,file_name)
        link_path = './book/service/attachments/%s/' % source
        link_path = '%s%s.mp4' %(link_path,file_name)
        log.info('save_path=%s' %save_path)
        with open(save_path, 'wb') as fd:
            for chunk in resp.iter_content(1024):
                fd.write(chunk)
    elif isinstance(msg, ShortVideoMessage):
        try:
            config = WxConfig.objects.get(key='book_auto_reply_short_video',status='1',category='3')
        except WxConfig.DoesNotExist:
            config = WxConfig()
            config.key = 'book_auto_reply_short_video'
            config.value = '我们已经收到您的短视频。'
            config.status = '1'
            config.category = '3'
            config.save()
        reply_msg = config.value
        response = TextReply(content=reply_msg, message=msg)
        receive_msg = '收到短视频(%s)' %msg.type
        resp = wechat.media.download(msg.media_id)
        save_path = '%s%s.mp4' %(save_path,file_name)
        link_path = './book/service/attachments/%s/' % source
        link_path = '%s%s.mp4' %(link_path,file_name)
        log.info('save_path=%s' %save_path)
        with open(save_path, 'wb') as fd:
            for chunk in resp.iter_content(1024):
                fd.write(chunk)
    elif isinstance(msg, BaseEvent):  # 事件信息
        log.info('msg.event=%s' % msg.event)
        if msg.event == 'scan': # 关注用户扫描事件
            pass
        elif msg.event == 'subscribe' or msg.event == 'subscribe_scan':
            try:
                config = WxConfig.objects.get(key='book_auto_reply_subscribe', category='3', reply_type='text', status = '1')
            except WxConfig.DoesNotExist:
                config = WxConfig()
                config.key = 'book_auto_reply_subscribe'
                config.value = '感谢关注我们！'
                config.status = '1'
                config.category = '3'
                config.reply_type = 'text'
                config.save()
            if config.status == '1':
                 response = TextReply(content=reply_msg, message=msg)
            try:
                config = WxConfig.objects.get(key='book_auto_reply_subscribe_card', category='3', reply_type='news')
            except WxConfig.DoesNotExist:
                config = WxConfig()
                config.key = 'book_auto_reply_subscribe_card'
                config.value = None
                config.status = '0'
                config.category = '3'
                config.reply_type = 'news'
                config.save()
            if config.status == '1':
                response = ArticlesReply(message=msg, articles=eval(config.value))
            receive_msg = '新用户关注事件(%s)' %msg.event
        elif msg.event == 'unsubscribe':
            receive_msg = '用户取消关注事件(%s)' %msg.event
        elif msg.event == 'click':
            if msg.key == 'XXXX':
                pass
            else:
                try:
                    config = WxConfig.objects.get(key='book_%s' %msg.key,status='1',category='3')
                except WxConfig.DoesNotExist:
                    config = WxConfig()
                    config.key = 'book_%s' %msg.key
                    config.value = '创建事件(click)变量(key)[book_%s],请设置响应内容' %msg.key
                    config.status = '1'
                    config.category = '3'
                    config.save()
                receive_msg = '%s(%s)' %(msg.key,msg.event)
                if config.reply_type == 'text':
                    reply_msg = config.value
                    response = TextReply(content=reply_msg, message=msg)
                elif config.reply_type == 'news':
                    response = ArticlesReply(message=msg, articles=eval(config.value))
                else: # 默认发送文本
                    pass
            receive_msg = '用户请求click事件，key=(%s)' %msg.key
        elif msg.event == 'view':
            receive_msg = '用户请求页面事件(%s|%s)' %(msg.event,msg.url)
        elif msg.event == 'templatesendjobfinish':
            receive_msg = None
        elif msg.event == 'kf_create_session':
            receive_msg = '进入客服会话模式(%s)' %msg.event
        elif msg.event == 'kf_close_session':
            receive_msg = '退出客服会话模式(%s)' %msg.event
        else:
            receive_msg = '用户触发未知类型事件(%s)' %msg.event
    else:
        try:
            config = WxConfig.objects.get(key='book_auto_kefu_offline',status='1',category='3')
        except WxConfig.DoesNotExist:
            config = WxConfig()
            config.key = 'book_auto_kefu_offline'
            config.value = '我们已经收到您的未知类型文件。\n谢谢，祝您生活愉快!'
            config.status = '1'
            config.category = '3'
            config.save()
        reply_msg = config.value
        response = TextReply(content=reply_msg, message=msg)
        receive_msg = '未知类型(%s)' %msg.event
    if receive_msg:
        try:
            wechat.message.send_text(book_service_admin.value, receive_msg, account=None)
        except WeChatClientException:
            log.warn('admin response out of time limit or subscription is canceled')
            log.info(receive_msg)
        # xml = response.render()
        # print(xml)
    return HttpResponse(response)


@csrf_exempt
def subscription(request):
    log.info('function subscription reload')
    wechat = get_book_subscription_wechat_client()
    echostr = request.GET.get('echostr', None)
    signature = request.GET.get('signature')
    msg_signature = request.GET.get('msg_signature')
    timestamp = request.GET.get('timestamp')
    nonce = request.GET.get('nonce')
    if request.method == 'GET' and echostr is not None and echostr != '':
        log.info('Starting check_signature ...')
        try:
            check_signature(BOOK_SUBSCRIPTION_TOKEN, signature, timestamp, nonce)
            return HttpResponse(echostr, content_type="text/plain")
        except InvalidSignatureException:
            return HttpResponseForbidden()
    xml = request.body
    # log.info('xml=%s' %xml)
    crypto = WeChatCrypto(BOOK_SUBSCRIPTION_TOKEN, BOOK_SUBSCRIPTION_ENCODING_AES_KEY, BOOK_SUBSCRIPTION_APPID)
    try:
        decrypted_xml = crypto.decrypt_message(xml, msg_signature, timestamp, nonce)
    except (InvalidAppIdException, InvalidSignatureException):
        return HttpResponseForbidden()
    msg = parse_message(decrypted_xml)
    source = msg.source
    log.info('#' * 8 + 'book subscription user [%s], msg.type:%s' %(source, msg.type) + '#' * 8)
    if isinstance(msg, TextMessage):
        log.info('Received type(%s) msg: %s' %(msg.type, msg.content))
    if isinstance(msg, BaseEvent):
        log.info('Received type(%s) msg: %s' %(msg.type, msg.event))
    log.info('#' * 80)
    if isinstance(msg, UnsubscribeEvent):
        redis_instance.delete(source)
        # notify admin
        return HttpResponse('unsubscribe')
    elif isinstance(msg, SubscribeEvent):
        redis_instance.set(source, sid())
    response = None
    reply_msg = receive_msg = ''

    save_path = './media/book/subscription/attachments/%s/' % source
    link_path = None
    file_name = sid()
    if not os.path.exists(save_path):
        os.makedirs(save_path)
    book_subscription_admin, book_subscription_admin_created = WxConfig.objects.get_or_create(key='book_subscription_admin',status='1',category='3')
    if isinstance(msg, TextMessage):
        receive_text = msg.content.strip()
        if book_subscription_admin is not None and source == book_subscription_admin.value:
            if receive_text == 'update_menu':
                menu_config, menu_config_created = WxConfig.objects.get_or_create(key='book_menu', status='1', category='4')
                if menu_config_created:
                    response = TextReply(content='新建菜单变量[book_menu],请设置value', message=msg)
                else:
                    wechat.menu.create(eval(menu_config.value))
                    response = TextReply(content='微信菜单更新成功！', message=msg)
            else:
                try:
                    config = WxConfig.objects.get(key='book_%s' %receive_text,status='1',category='3')
                    if config.reply_type == 'text':
                        reply_msg = config.value
                        response = TextReply(content=reply_msg, message=msg)
                    elif config.reply_type == 'news':
                        response = ArticlesReply(articles=eval(config.value), message=msg)
                    elif config.reply_type == 'voice':
                        pass
                    elif config.reply_type == 'image':
                        pass
                    elif config.reply_type == 'video':
                        pass
                except WxConfig.DoesNotExist:
                    config = WxConfig()
                    config.key = 'book_%s' %receive_text
                    config.value = 'book_%s' %receive_text
                    config.status = '1'
                    config.category = '3'
                    config.save()
                    response = TextReply(content='新建微信自定义字符串[%s]' %config.key, message=msg)
        else:
            try:
                config = WxConfig.objects.get(key='book_%s' %receive_text,status='1',category='3')
            except WxConfig.DoesNotExist:
                try:
                    config = WxConfig.objects.get(key='book_auto_reply_text',status='1',category='3')
                except WxConfig.DoesNotExist:
                    config = WxConfig()
                    config.key = 'book_auto_reply_text'
                    config.value = '我们已经收到您的留言。谢谢！'
                    config.status = '1'
                    config.category = '3'
                    config.save()
            receive_msg = '%s(%s)' %(receive_text, msg.type)
            if config.reply_type == 'text':
                response = TextReply(content=config.value, message=msg)
            elif config.reply_type == 'news':
                response = ArticlesReply(articles=eval(config.value), message=msg)
            elif config.reply_type == 'voice':
                pass
            elif config.reply_type == 'image':
                pass
            elif config.reply_type == 'video':
                pass
    elif isinstance(msg, VoiceMessage):
        receive_text = msg.recognition
        try:
            config = WxConfig.objects.get(key='book_%s' %receive_text, status='1', category='3')
        except WxConfig.DoesNotExist:
            try:
                config = WxConfig.objects.get(key='book_auto_reply_voice',status='1',category='3')
            except WxConfig.DoesNotExist:
                config = WxConfig()
                config.key = 'book_auto_reply_voice'
                config.value = '我们已经收到您的语音留言。'
                config.status = '1'
                config.category = '3'
                config.save()
        receive_msg = '%s(%s)' %(receive_text, msg.type)
        reply_msg = config.value
        response = TextReply(content=reply_msg, message=msg)
        resp = wechat.media.download(msg.media_id)
        save_path = '%s%s.%s' %(save_path, file_name, msg.format)
        link_path = './book/subscription/attachments/%s/' % source
        link_path = '%s%s.amr' %(link_path,file_name)
        log.info('save_path=%s' %save_path) # file_path=./book/subscription/attachments/jezhang/150611114353137791.jpg
        with open(save_path, 'wb') as fd:
            for chunk in resp.iter_content(1024):
                fd.write(chunk)
    elif isinstance(msg, ImageMessage):
        try:
            config = WxConfig.objects.get(key='book_auto_reply_image',status='1',category='3')
        except WxConfig.DoesNotExist:
            config = WxConfig()
            config.key = 'book_auto_reply_image'
            config.value = '我们已经收到您的图片。'
            config.status = '1'
            config.category = '3'
            config.save()
        reply_msg = config.value
        response = TextReply(content=reply_msg, message=msg)
        receive_msg = '收到图片(%s)' %msg.type
        resp = wechat.media.download(msg.media_id)
        save_path = '%s%s.jpg' %(save_path,file_name)
        link_path = './book/subscription/attachments/%s/' % source
        link_path = '%s%s.jpg' %(link_path,file_name)
        log.info('save_path=%s' %save_path)
        with open(save_path, 'wb') as fd:
            for chunk in resp.iter_content(1024):
                fd.write(chunk)
    elif isinstance(msg, VideoMessage):
        try:
            config = WxConfig.objects.get(key='book_auto_reply_video',status='1',category='3')
        except WxConfig.DoesNotExist:
            config = WxConfig()
            config.key = 'book_auto_reply_video'
            config.value = '我们已经收到您的视频。'
            config.status = '1'
            config.category = '3'
            config.save()
        reply_msg = config.value
        response = TextReply(content=reply_msg, message=msg)
        receive_msg = '收到视频(%s)' %msg.type
        resp = wechat.media.download(msg.media_id)
        save_path = '%s%s.mp4' %(save_path,file_name)
        link_path = './book/subscription/attachments/%s/' % source
        link_path = '%s%s.mp4' %(link_path,file_name)
        log.info('save_path=%s' %save_path)
        with open(save_path, 'wb') as fd:
            for chunk in resp.iter_content(1024):
                fd.write(chunk)
    elif isinstance(msg, ShortVideoMessage):
        try:
            config = WxConfig.objects.get(key='book_auto_reply_short_video',status='1',category='3')
        except WxConfig.DoesNotExist:
            config = WxConfig()
            config.key = 'book_auto_reply_short_video'
            config.value = '我们已经收到您的短视频。'
            config.status = '1'
            config.category = '3'
            config.save()
        reply_msg = config.value
        response = TextReply(content=reply_msg, message=msg)
        receive_msg = '收到短视频(%s)' %msg.type
        resp = wechat.media.download(msg.media_id)
        save_path = '%s%s.mp4' %(save_path,file_name)
        link_path = './book/subscription/attachments/%s/' % source
        link_path = '%s%s.mp4' %(link_path,file_name)
        log.info('save_path=%s' %save_path)
        with open(save_path, 'wb') as fd:
            for chunk in resp.iter_content(1024):
                fd.write(chunk)
    elif isinstance(msg, BaseEvent):  # 事件信息
        log.info('msg.event=%s' % msg.event)
        if msg.event == 'scan': # 关注用户扫描事件
            pass
        elif msg.event == 'subscribe' or msg.event == 'subscribe_scan':
            try:
                config = WxConfig.objects.get(key='book_auto_reply_subscribe', category='3', reply_type='text', status = '1')
            except WxConfig.DoesNotExist:
                config = WxConfig()
                config.key = 'book_auto_reply_subscribe'
                config.value = '感谢关注我们！'
                config.status = '1'
                config.category = '3'
                config.reply_type = 'text'
                config.save()
            if config.status == '1':
                 response = TextReply(content=reply_msg, message=msg)
            try:
                config = WxConfig.objects.get(key='book_auto_reply_subscribe_card', category='3', reply_type='news')
            except WxConfig.DoesNotExist:
                config = WxConfig()
                config.key = 'book_auto_reply_subscribe_card'
                config.value = None
                config.status = '0'
                config.category = '3'
                config.reply_type = 'news'
                config.save()
            if config.status == '1':
                response = ArticlesReply(message=msg, articles=eval(config.value))
            receive_msg = '新用户关注事件(%s)' %msg.event
        elif msg.event == 'unsubscribe':
            receive_msg = '用户取消关注事件(%s)' %msg.event
        elif msg.event == 'click':
            if msg.key == 'XXXX':
                pass
            else:
                try:
                    config = WxConfig.objects.get(key='book_%s' %msg.key,status='1',category='3')
                except WxConfig.DoesNotExist:
                    config = WxConfig()
                    config.key = 'book_%s' %msg.key
                    config.value = '创建事件(click)变量(key)[book_%s],请设置响应内容' %msg.key
                    config.status = '1'
                    config.category = '3'
                    config.save()
                receive_msg = '%s(%s)' %(msg.key,msg.event)
                if config.reply_type == 'text':
                    reply_msg = config.value
                    response = TextReply(content=reply_msg, message=msg)
                elif config.reply_type == 'news':
                    response = ArticlesReply(message=msg, articles=eval(config.value))
                else: # 默认发送文本
                    pass
            receive_msg = '用户请求click事件，key=(%s)' %msg.key
        elif msg.event == 'view':
            receive_msg = '用户请求页面事件(%s|%s)' %(msg.event,msg.url)
        elif msg.event == 'templatesendjobfinish':
            receive_msg = None
        elif msg.event == 'kf_create_session':
            receive_msg = '进入客服会话模式(%s)' %msg.event
        elif msg.event == 'kf_close_session':
            receive_msg = '退出客服会话模式(%s)' %msg.event
        else:
            receive_msg = '用户触发未知类型事件(%s)' %msg.event
    else:
        try:
            config = WxConfig.objects.get(key='book_auto_kefu_offline',status='1',category='3')
        except WxConfig.DoesNotExist:
            config = WxConfig()
            config.key = 'book_auto_kefu_offline'
            config.value = '我们已经收到您的未知类型文件。\n谢谢，祝您生活愉快!'
            config.status = '1'
            config.category = '3'
            config.save()
        reply_msg = config.value
        response = TextReply(content=reply_msg, message=msg)
        receive_msg = '未知类型(%s)' %msg.event
    if receive_msg:
        try:
            wechat.message.send_text(book_subscription_admin.value, receive_msg, account=None)
        except WeChatClientException:
            log.warn('admin response out of time limit or subscription is canceled')
            log.info(receive_msg)
        # xml = response.render()
        # print(xml)
    return HttpResponse(response)


def get_book_subscription_jssdk_signature(request):
    if DEBUG:
        return None
    wechat = get_book_subscription_wechat_client()
    jsapi_ticket = wechat.jsapi.get_jsapi_ticket()
    # print('jsapi_ticket=%s' %jsapi_ticket)
    nonce_str= ''.join(random.choice(string.ascii_letters + string.digits) for _ in range(15))
    # print('noncestr=%s' %nonce_str)
    timestamp_int = int(time.time())
    # print('timestamp=%d' %timestamp_int)
    # url = 'http://' + request.META.get('HTTP_HOST')+request.META.get('PATH_INFO')+request.META.get('QUERY_STRING','')
    url = 'https://' + request.META.get('HTTP_HOST')+request.META.get('PATH_INFO')
    # print('url=%s' %url)
    tmpstr = 'jsapi_ticket=%s&noncestr=%s&timestamp=%d&url=%s' %(jsapi_ticket,nonce_str,timestamp_int,url)
    tmpstr = tmpstr.encode('utf-8') # python3 need this line
    tmpstr = hashlib.sha1(tmpstr).hexdigest() # verify at http://mp.weixin.qq.com/debug/cgi-bin/sandbox?t=jsapisign
    # print('signature=%s' %tmpstr)
    jssdk_signature = {}
    jssdk_signature['timestamp']  = timestamp_int
    jssdk_signature['nonce'] = nonce_str
    jssdk_signature['signature'] = tmpstr
    jssdk_signature['appid'] = BOOK_SUBSCRIPTION_APPID
    return jssdk_signature

